package com.csoft.riskroll;

import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TextView;
import android.widget.Toast;

/**
 * RiskRoll v 1.1
 * @author John Cline
 * 16 October 2010
 *
 * This is the main 1.0 feature, the "Auto-roll" activity. The activity
 * will allow the user to enter the army sizes for each side, attack and defense,
 * and will roll it out automatically until defense is beaten or attack is
 * at a user-inputed size.
 * 
 * Dice icon obtained from http://www.psdgraphics.com/
 * This code is distributed under Apache v2, available http://www.apache.org/licenses/LICENSE-2.0
 */

public class RiskAutoRoll extends Activity {

	private Button rollBut;
	private Button[] attackArmyButs, stopArmyButs, defendArmyButs;
	private EditText attackArmyText, stopArmyText, defendArmyText;
	private TextView outputBox;
	private int attackCount, defendCount, stopCount;
	private String eol;
	private RiskDie dieSet;
    private Toast toastWin;
	
	private static final int CHANGE_BUTTONS_SIZE = 6;
    private static final String SAVED_OUTPUT = "";
	private static final String ERROR_ARMY_COUNT = "Army size is too small. Please correct.";
	
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        /*
         * Setups up the initial view elements and 
         * calls the variable initiation function.
         */
        setContentView(R.layout.autoroll);
        rollBut = (Button) findViewById(R.id.autoRollBut);
        attackArmyText = (EditText) findViewById(R.id.attackArmyText);
        stopArmyText = (EditText) findViewById(R.id.attackStopText);
        defendArmyText = (EditText) findViewById(R.id.defendArmyText);
        outputBox = (TextView) findViewById(R.id.outputBox);
        initVars();
    }

	private void initVars() {
		attackArmyButs = new Button[CHANGE_BUTTONS_SIZE];
		stopArmyButs = new Button[CHANGE_BUTTONS_SIZE];
		defendArmyButs = new Button[CHANGE_BUTTONS_SIZE];
		attackArmyButs[0] = (Button) findViewById(R.id.attackArmyMTBut);
		attackArmyButs[1] = (Button) findViewById(R.id.attackArmyMFBut);
		attackArmyButs[2] = (Button) findViewById(R.id.attackArmyMOBut);
		attackArmyButs[3] = (Button) findViewById(R.id.attackArmyPOBut);
		attackArmyButs[4] = (Button) findViewById(R.id.attackArmyPFBut);
		attackArmyButs[5] = (Button) findViewById(R.id.attackArmyPTBut);
		stopArmyButs[0] = (Button) findViewById(R.id.attackStopMTBut);
		stopArmyButs[1] = (Button) findViewById(R.id.attackStopMFBut);
		stopArmyButs[2] = (Button) findViewById(R.id.attackStopMOBut);
		stopArmyButs[3] = (Button) findViewById(R.id.attackStopPOBut);
		stopArmyButs[4] = (Button) findViewById(R.id.attackStopPFBut);
		stopArmyButs[5] = (Button) findViewById(R.id.attackStopPTBut);
		defendArmyButs[0] = (Button) findViewById(R.id.defendArmyMTBut);
		defendArmyButs[1] = (Button) findViewById(R.id.defendArmyMFBut);
		defendArmyButs[2] = (Button) findViewById(R.id.defendArmyMOBut);
		defendArmyButs[3] = (Button) findViewById(R.id.defendArmyPOBut);
		defendArmyButs[4] = (Button) findViewById(R.id.defendArmyPFBut);
		defendArmyButs[5] = (Button) findViewById(R.id.defendArmyPTBut);
		
		rollBut.setOnClickListener(new OnClickListener () {
        	public void onClick(View v) {
        		rollItOut();
        	}
        });
		
		for (int i=0;i<CHANGE_BUTTONS_SIZE;i++) {
			attackArmyButs[i].setOnClickListener(new OnClickListener () {
				public void onClick(View v) {
					changeFields(v);
				}
			});
			stopArmyButs[i].setOnClickListener(new OnClickListener () {
				public void onClick(View v) {
					changeFields(v);
				}
			});
			defendArmyButs[i].setOnClickListener(new OnClickListener () {
				public void onClick(View v) {
					changeFields(v);
				}
			});
		}
		updateArmyCounts();
		dieSet = new RiskDie(1,1);
		eol = new String(System.getProperty("line.separator"));
	}
	
	private void changeFields(View v) {
		switch (v.getId()) {
			case R.id.attackArmyMTBut: 
				if (attackArmyText.getText().toString().equals("")) {
					attackArmyText.setText(Integer.toString(-10)); break;
				} else {
					attackArmyText.setText(Integer.toString(Integer.parseInt(attackArmyText.getText().toString()) - 10)); break;
				}
			case R.id.attackArmyMFBut: 
				if (attackArmyText.getText().toString().equals("")) {
					attackArmyText.setText(Integer.toString(-5)); break;
				} else {
					attackArmyText.setText(Integer.toString(Integer.parseInt(attackArmyText.getText().toString()) - 5)); break;
				}
			case R.id.attackArmyMOBut: 
				if (attackArmyText.getText().toString().equals("")) {
					attackArmyText.setText(Integer.toString(-1)); break;
				} else {
					attackArmyText.setText(Integer.toString(Integer.parseInt(attackArmyText.getText().toString()) - 1)); break;
				}
			case R.id.attackArmyPOBut: 
				if (attackArmyText.getText().toString().equals("")) {
					attackArmyText.setText(Integer.toString(1)); break;
				} else {
					attackArmyText.setText(Integer.toString(Integer.parseInt(attackArmyText.getText().toString()) + 1)); break;
				}			
			case R.id.attackArmyPFBut: 
				if (attackArmyText.getText().toString().equals("")) {
					attackArmyText.setText(Integer.toString(5)); break;
				} else {
					attackArmyText.setText(Integer.toString(Integer.parseInt(attackArmyText.getText().toString()) + 5)); break;
				}
			case R.id.attackArmyPTBut: 
				if (attackArmyText.getText().toString().equals("")) {
					attackArmyText.setText(Integer.toString(10)); break;
				} else {
					attackArmyText.setText(Integer.toString(Integer.parseInt(attackArmyText.getText().toString()) + 10)); break;
				}
			case R.id.attackStopMTBut:
				if (stopArmyText.getText().toString().equals("")) {
					stopArmyText.setText(Integer.toString(-10)); break;
				} else {
					stopArmyText.setText(Integer.toString(Integer.parseInt(stopArmyText.getText().toString()) - 10)); break;
				}
			case R.id.attackStopMFBut: 
				if (stopArmyText.getText().toString().equals("")) {
					stopArmyText.setText(Integer.toString(-5)); break;
				} else {
					stopArmyText.setText(Integer.toString(Integer.parseInt(stopArmyText.getText().toString()) - 5)); break;
				}
			case R.id.attackStopMOBut: 
				if (stopArmyText.getText().toString().equals("")) {
					stopArmyText.setText(Integer.toString(-1)); break;
				} else {
					stopArmyText.setText(Integer.toString(Integer.parseInt(stopArmyText.getText().toString()) - 1)); break;
				}
			case R.id.attackStopPOBut: 
				if (stopArmyText.getText().toString().equals("")) {
					stopArmyText.setText(Integer.toString(1)); break;
				} else {
					stopArmyText.setText(Integer.toString(Integer.parseInt(stopArmyText.getText().toString()) + 1)); break;
				}
			case R.id.attackStopPFBut: 
				if (stopArmyText.getText().toString().equals("")) {
					stopArmyText.setText(Integer.toString(5)); break;
				} else {
					stopArmyText.setText(Integer.toString(Integer.parseInt(stopArmyText.getText().toString()) + 5)); break;
				}
			case R.id.attackStopPTBut: 
				if (stopArmyText.getText().toString().equals("")) {
					stopArmyText.setText(Integer.toString(10)); break;
				} else {
					stopArmyText.setText(Integer.toString(Integer.parseInt(stopArmyText.getText().toString()) + 10)); break;
				}
			case R.id.defendArmyMTBut:
				if (defendArmyText.getText().toString().equals("")) {
					defendArmyText.setText(Integer.toString(-10)); break;
				} else {
					defendArmyText.setText(Integer.toString(Integer.parseInt(defendArmyText.getText().toString()) - 10)); break;
				}
			case R.id.defendArmyMFBut: 
				if (defendArmyText.getText().toString().equals("")) {
					defendArmyText.setText(Integer.toString(-5)); break;
				} else {
					defendArmyText.setText(Integer.toString(Integer.parseInt(defendArmyText.getText().toString()) - 5)); break;
				}
			case R.id.defendArmyMOBut: 
				if (defendArmyText.getText().toString().equals("")) {
					defendArmyText.setText(Integer.toString(-1)); break;
				} else {
					defendArmyText.setText(Integer.toString(Integer.parseInt(defendArmyText.getText().toString()) - 1)); break;
				}
			case R.id.defendArmyPOBut: 
				if (defendArmyText.getText().toString().equals("")) {
					defendArmyText.setText(Integer.toString(1)); break;
				} else {
					defendArmyText.setText(Integer.toString(Integer.parseInt(defendArmyText.getText().toString()) + 1)); break;
				}
			case R.id.defendArmyPFBut: 
				if (defendArmyText.getText().toString().equals("")) {
					defendArmyText.setText(Integer.toString(5)); break;
				} else {
					defendArmyText.setText(Integer.toString(Integer.parseInt(defendArmyText.getText().toString()) + 5)); break;
				}
			case R.id.defendArmyPTBut: 
				if (defendArmyText.getText().toString().equals("")) {
					defendArmyText.setText(Integer.toString(10)); break;
				} else {
					defendArmyText.setText(Integer.toString(Integer.parseInt(defendArmyText.getText().toString()) + 10)); break;
				}
		}	
		updateArmyCounts();
	}

	private void updateArmyCounts() {
		if (!attackArmyText.getText().toString().equals(""))
			attackCount = Integer.parseInt(attackArmyText.getText().toString());
		if (!stopArmyText.getText().toString().equals(""))
			stopCount = Integer.parseInt(stopArmyText.getText().toString());
		if (!defendArmyText.getText().toString().equals(""))
			defendCount = Integer.parseInt(defendArmyText.getText().toString());
	}

	private void rollItOut() {
		updateArmyCounts();
		int curAttackDie, curDefendDie;
		int[] results, resultDie;
		String outputResults = "";
		if (((attackCount <= 1) || (stopCount < 1)) || (defendCount <= 0)) {
			displayNotification(ERROR_ARMY_COUNT);
		} else {
			while ((attackCount > stopCount) && (defendCount > 0)) {
				if (attackCount >= (3 + stopCount)) curAttackDie = 3;
				else if (attackCount == (2 + stopCount)) curAttackDie = 2;
				else curAttackDie = 1;
				if (defendCount >= 2) curDefendDie = 2;
				else curDefendDie = 1;
				dieSet.setNumDie(curAttackDie, curDefendDie);
				results = dieSet.rollDie();
				if (results[0] == -1) displayNotification("Error rolling.");
				else {
					resultDie = dieSet.getAttackDie();
			    	outputResults = outputResults + "A: ";
			    	for (int i=0;i<dieSet.getAttackCount();i++) {
			    		outputResults += Integer.toString(resultDie[i]) + " ";
			    	}
			    	resultDie = dieSet.getDefendDie();
			    	outputResults = outputResults + "D: ";
			    	for (int i=0;i<dieSet.getDefendCount();i++) {
			    		outputResults += Integer.toString(resultDie[i]) + " ";
			    	}
			    	outputResults += " || ";
			    	if (results[0] == 0) {
			    		outputResults += "Defense lose " + Integer.toString(results[1]) + " ";
			    	} else {
			    		outputResults += "Attack lose " + Integer.toString(results[0]) + " ";
			    		if (results[1] != 0) {
			        		outputResults += "Defense lose " + Integer.toString(results[1]) + " ";
			        	}
			    	}
			    	outputResults = outputResults + eol;
					attackCount -= results[0];
					defendCount -= results[1];
				}
			}
			outputResults += "Attack final count: " + Integer.toString(attackCount) + eol;
			outputResults += "Defend final count: " + Integer.toString(defendCount) + eol;
			outputBox.setText(outputResults);
		}	
	}
	
	private void displayNotification(String msg) {
		/*
		 * Displays a toast popup with the text contained in msg.
		 */
		toastWin = Toast.makeText(getApplicationContext(), msg, Toast.LENGTH_LONG);
		toastWin.show();
	}
	
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
    	/*
    	 * Creates the options menu from the options.xml file.
    	 */
        MenuInflater inflater = getMenuInflater();
        inflater.inflate(R.menu.options_menu, menu);
        return true;
    }
	
    public boolean onOptionsItemSelected(MenuItem item) {
    	/*
    	 * Figures out which option was selected, and loads accordingly.
    	 */
    	switch (item.getItemId()) {
    		case R.id.switch_screen:
    			startActivity(new Intent(this, RiskRoll.class));
    			this.finish();
    			return true;
	        case R.id.options:
	            startActivity(new Intent(this, Preferences.class));
	            return true;
	        case R.id.quit:
	            this.finish();
	            return true;
        }
        return false;
    }
    
    @Override  
    protected void onRestoreInstanceState(Bundle savedInstanceState) {  
    	super.onRestoreInstanceState(savedInstanceState);
    	/*
    	 * Restores settings on return to the application, specifically
    	 * the number of die and any output text left in the window.
    	 */
    	outputBox.setText(savedInstanceState.getString(SAVED_OUTPUT));
    }  

	@Override  
    protected void onSaveInstanceState(Bundle outState) {   
		super.onSaveInstanceState(outState); 
		/*
    	 * Saves settings on exit of the application, specifically
    	 * the number of die and any output text left in the window.
    	 */
		outState.putString(SAVED_OUTPUT, (String) outputBox.getText());  
    }
}
